#!/bin/bash

# JDFS2 Test Script
# 运行Go测试用例

set -e  # 遇到错误立即退出

# 颜色定义
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
BLUE='\033[0;34m'
NC='\033[0m' # No Color

# 打印带颜色的消息
print_info() {
    echo -e "${BLUE}[INFO]${NC} $1"
}

print_success() {
    echo -e "${GREEN}[SUCCESS]${NC} $1"
}

print_warning() {
    echo -e "${YELLOW}[WARNING]${NC} $1"
}

print_error() {
    echo -e "${RED}[ERROR]${NC} $1"
}

# 检查Go环境
check_go() {
    if ! command -v go &> /dev/null; then
        print_error "Go is not installed or not in PATH"
        exit 1
    fi
    
    GO_VERSION=$(go version | awk '{print $3}')
    print_info "Using Go version: $GO_VERSION"
}

# 运行单元测试
run_tests() {
    local PACKAGE="$1"
    local VERBOSE="$2"
    local COVERAGE="$3"
    
    print_info "Running tests for: ${PACKAGE:-"all packages"}"
    
    # 构建测试命令
    TEST_CMD="go test"
    
    if [ "$VERBOSE" = true ]; then
        TEST_CMD="$TEST_CMD -v"
    fi
    
    if [ "$COVERAGE" = true ]; then
        TEST_CMD="$TEST_CMD -coverprofile=coverage.out -covermode=atomic"
    fi
    
    if [ -n "$PACKAGE" ]; then
        TEST_CMD="$TEST_CMD ./$PACKAGE"
    else
        TEST_CMD="$TEST_CMD ./..."
    fi
    
    # 执行测试
    print_info "Executing: $TEST_CMD"
    
    if eval "$TEST_CMD"; then
        print_success "Tests passed for: ${PACKAGE:-"all packages"}"
        return 0
    else
        print_error "Tests failed for: ${PACKAGE:-"all packages"}"
        return 1
    fi
}

# 生成覆盖率报告
generate_coverage() {
    local VERBOSE="$1"
    
    if [ ! -f "coverage.out" ]; then
        print_warning "No coverage file found, running tests with coverage..."
        run_tests "" false true
    fi
    
    print_info "Generating coverage report..."
    
    # 显示覆盖率统计
    if [ "$VERBOSE" = true ]; then
        if go tool cover -func=coverage.out; then
            print_success "Coverage statistics generated"
        else
            print_error "Failed to generate coverage statistics"
            return 1
        fi
    else
        # 静默模式，只显示总体覆盖率
        if go tool cover -func=coverage.out | tail -1; then
            print_success "Coverage statistics generated"
        else
            print_error "Failed to generate coverage statistics"
            return 1
        fi
    fi
    
    # 生成HTML报告
    if go tool cover -html=coverage.out -o coverage.html; then
        print_success "HTML coverage report generated: coverage.html"
    else
        print_error "Failed to generate HTML coverage report"
        return 1
    fi
}

# 运行特定类型的测试
run_test_type() {
    local TEST_TYPE="$1"
    local VERBOSE="$2"
    
    case "$TEST_TYPE" in
        "unit")
            print_info "Running unit tests..."
            run_tests "" "$VERBOSE" false
            ;;
        "integration")
            print_info "Running integration tests..."
            run_tests "internal/service" "$VERBOSE" false
            ;;
        "storage")
            print_info "Running storage tests..."
            run_tests "internal/storage" "$VERBOSE" false
            ;;
        "concurrent")
            print_info "Running concurrent tests..."
            run_tests "internal/storage" "$VERBOSE" false
            ;;
        "all")
            print_info "Running all tests..."
            run_tests "" "$VERBOSE" true
            generate_coverage "$VERBOSE"
            ;;
        *)
            print_error "Unknown test type: $TEST_TYPE"
            return 1
            ;;
    esac
}

# 清理测试文件
cleanup() {
    print_info "Cleaning up test artifacts..."
    rm -f coverage.out coverage.html
    print_success "Cleanup completed"
}

# 显示帮助信息
show_help() {
    echo "JDFS2 Test Script"
    echo ""
    echo "Usage: $0 [OPTIONS] [TEST_TYPE]"
    echo ""
    echo "Options:"
    echo "  -h, --help       Show this help message"
    echo "  -v, --verbose    Verbose output"
    echo "  -c, --coverage   Generate coverage report"
    echo "  -p, --package    Test specific package (e.g., internal/storage)"
    echo "  --clean          Clean test artifacts"
    echo ""
    echo "Test Types:"
    echo "  unit            Run unit tests only"
    echo "  integration     Run integration tests"
    echo "  storage         Run storage layer tests"
    echo "  concurrent      Run concurrent safety tests"
    echo "  all             Run all tests with coverage (default)"
    echo ""
    echo "Examples:"
    echo "  $0                           # Run all tests with coverage"
    echo "  $0 -v                        # Run all tests with verbose output"
    echo "  $0 -c                        # Run tests and generate coverage"
    echo "  $0 -p internal/storage       # Test specific package"
    echo "  $0 storage -v                # Run storage tests with verbose output"
    echo "  $0 --clean                   # Clean test artifacts"
}

# 主函数
main() {
    local VERBOSE=false
    local COVERAGE=false
    local PACKAGE=""
    local TEST_TYPE="all"
    local CLEAN=false
    
    # 解析命令行参数
    while [[ $# -gt 0 ]]; do
        case $1 in
            -h|--help)
                show_help
                exit 0
                ;;
            -v|--verbose)
                VERBOSE=true
                shift
                ;;
            -c|--coverage)
                COVERAGE=true
                shift
                ;;
            -p|--package)
                PACKAGE="$2"
                shift 2
                ;;
            --clean)
                CLEAN=true
                shift
                ;;
            unit|integration|storage|concurrent|all)
                TEST_TYPE="$1"
                shift
                ;;
            *)
                print_error "Unknown option: $1"
                show_help
                exit 1
                ;;
        esac
    done
    
    # 设置详细输出
    if [ "$VERBOSE" = true ]; then
        set -x
    fi
    
    print_info "Starting JDFS2 test process..."
    
    # 检查Go环境
    check_go
    
    # 清理（如果需要）
    if [ "$CLEAN" = true ]; then
        cleanup
        exit 0
    fi
    
    # 运行测试
    if [ -n "$PACKAGE" ]; then
        # 测试特定包
        run_tests "$PACKAGE" "$VERBOSE" "$COVERAGE"
    else
        # 运行特定类型的测试
        run_test_type "$TEST_TYPE" "$VERBOSE"
    fi
    
    # 生成覆盖率报告（如果需要）
    # 注意：如果 TEST_TYPE="all"，已经在 run_test_type 中调用了 generate_coverage
    if [ "$COVERAGE" = true ] && [ -f "coverage.out" ] && [ "$TEST_TYPE" != "all" ]; then
        generate_coverage "$VERBOSE"
    fi
    
    print_success "Test process completed successfully!"
}

# 运行主函数
main "$@"
